package com.cherry.androidcode.demo

import android.os.Bundle
import android.util.Log
import android.view.View
import android.widget.TextView
import androidx.coordinatorlayout.widget.CoordinatorLayout
import androidx.core.view.ViewCompat
import com.cherry.androidcode.base.BaseActivity
import com.google.android.material.bottomsheet.BottomSheetBehavior
import kotlinx.android.synthetic.main.activity_behavior_demo.*


/**
 * 常用Behavior
 * BottomSheetBehavior
 *
 *
 * @author DongMS
 * @date 2019/7/2
 */
class BehaviorDemoActivity : BaseActivity() {

    private val TAG = this.javaClass.simpleName

    override val activityLayoutRes = com.cherry.androidcode.R.layout.activity_behavior_demo

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        //BottomSheetDialog ,BottomSheetDialogFragment用法不重复写了。。。
        val bottomSheetBehavior = BottomSheetBehavior.from<TextView>(tv_test_behavior)
        btn_show_bottom_sheet.setOnClickListener {
            if (bottomSheetBehavior.state == BottomSheetBehavior.STATE_EXPANDED) {
                //展开状态，隐藏
                bottomSheetBehavior.setState(BottomSheetBehavior.STATE_COLLAPSED)
            } else {
                //其他的状态展开
                bottomSheetBehavior.setState(BottomSheetBehavior.STATE_EXPANDED)
            }
        }
        bottomSheetBehavior.setBottomSheetCallback(object : BottomSheetBehavior.BottomSheetCallback() {
            //滑动的时候调用
            override fun onSlide(bottomSheet: View, slideOffset: Float) {
                Log.e(TAG, slideOffset.toString())
            }

            //状态改变的回调
            //STATE_COLLAPSED： 默认的折叠状态
            //STATE_DRAGGING ： 过渡状态
            //STATE_SETTLING: 视图从脱离手指自由滑动到最终停下的这一小段时间
            //STATE_EXPANDED： bottom sheet 处于完全展开的状态
            //STATE_HIDDEN ： 默认无此状态（可通过app:behavior_hideable 启用此状态），启用后用户将能通过向下滑动完全隐藏
            override fun onStateChanged(bottomSheet: View, newState: Int) {
                Log.e(TAG, newState.toString())
            }
        })

    }


    class TestBehavior : CoordinatorLayout.Behavior<View>() {
        /**
         * 表示是否给应用了Behavior 的View 指定一个依赖的布局，通常，当依赖的View 布局发生变化时
         * 不管被被依赖View 的顺序怎样，被依赖的View也会重新布局
         * @param parent
         * @param child 绑定behavior 的View
         * @param dependency   依赖的view
         * @return 如果child 是依赖的指定的View 返回true,否则返回false
         */
        override fun layoutDependsOn(parent: CoordinatorLayout, child: View, dependency: View): Boolean {
            return super.layoutDependsOn(parent, child, dependency)
        }

        /**
         * 当被依赖的View 状态（如：位置、大小）发生变化时，这个方法被调用
         * @param parent
         * @param child
         * @param dependency
         * @return
         */
        override fun onDependentViewChanged(parent: CoordinatorLayout, child: View, dependency: View): Boolean {
            return super.onDependentViewChanged(parent, child, dependency)
        }

        /**
         * 当coordinatorLayout 的子View试图开始嵌套滑动的时候被调用。当返回值为true的时候表明
         * coordinatorLayout 充当nested scroll parent 处理这次滑动，需要注意的是只有当返回值为true
         * 的时候，Behavior 才能收到后面的一些nested scroll 事件回调（如：onNestedPreScroll、onNestedScroll等）
         * 这个方法有个重要的参数nestedScrollAxes，表明处理的滑动的方向。
         *
         * @param coordinatorLayout 和Behavior 绑定的View的父CoordinatorLayout
         * @param child  和Behavior 绑定的View
         * @param directTargetChild
         * @param target
         * @param nestedScrollAxes 嵌套滑动 应用的滑动方向，看 [ViewCompat.SCROLL_AXIS_HORIZONTAL],
         * [ViewCompat.SCROLL_AXIS_VERTICAL]
         * @return
         */
        override fun onStartNestedScroll(coordinatorLayout: CoordinatorLayout, child: View, directTargetChild: View, target: View, nestedScrollAxes: Int): Boolean {
            return super.onStartNestedScroll(coordinatorLayout, child, directTargetChild, target, nestedScrollAxes)
        }

        /**
         * 嵌套滚动发生之前被调用
         * 在nested scroll child 消费掉自己的滚动距离之前，嵌套滚动每次被nested scroll child
         * 更新都会调用onNestedPreScroll。注意有个重要的参数consumed，可以修改这个数组表示你消费
         * 了多少距离。假设用户滑动了100px,child 做了90px 的位移，你需要把 consumed［1］的值改成90，
         * 这样coordinatorLayout就能知道只处理剩下的10px的滚动。
         * @param coordinatorLayout
         * @param child
         * @param target
         * @param dx  用户水平方向的滚动距离
         * @param dy  用户竖直方向的滚动距离
         * @param consumed
         */
        override fun onNestedPreScroll(coordinatorLayout: CoordinatorLayout, child: View, target: View, dx: Int, dy: Int, consumed: IntArray) {
            super.onNestedPreScroll(coordinatorLayout, child, target, dx, dy, consumed)
        }

        /**
         * 进行嵌套滚动时被调用
         * @param coordinatorLayout
         * @param child
         * @param target
         * @param dxConsumed target 已经消费的x方向的距离
         * @param dyConsumed target 已经消费的y方向的距离
         * @param dxUnconsumed x 方向剩下的滚动距离
         * @param dyUnconsumed y 方向剩下的滚动距离
         */
        override fun onNestedScroll(coordinatorLayout: CoordinatorLayout, child: View, target: View, dxConsumed: Int, dyConsumed: Int, dxUnconsumed: Int, dyUnconsumed: Int) {
            super.onNestedScroll(coordinatorLayout, child, target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed)
        }

        /**
         * 嵌套滚动结束时被调用，这是一个清除滚动状态等的好时机。
         * @param coordinatorLayout
         * @param child
         * @param target
         */
        override fun onStopNestedScroll(coordinatorLayout: CoordinatorLayout, child: View, target: View) {
            super.onStopNestedScroll(coordinatorLayout, child, target)
        }

        /**
         * onStartNestedScroll返回true才会触发这个方法，接受滚动处理后回调，可以在这个
         * 方法里做一些准备工作，如一些状态的重置等。
         * @param coordinatorLayout
         * @param child
         * @param directTargetChild
         * @param target
         * @param nestedScrollAxes
         */
        override fun onNestedScrollAccepted(coordinatorLayout: CoordinatorLayout, child: View, directTargetChild: View, target: View, nestedScrollAxes: Int) {
            super.onNestedScrollAccepted(coordinatorLayout, child, directTargetChild, target, nestedScrollAxes)
        }

        /**
         * 用户松开手指并且会发生惯性动作之前调用，参数提供了速度信息，可以根据这些速度信息
         * 决定最终状态，比如滚动Header，是让Header处于展开状态还是折叠状态。返回true 表
         * 示消费了fling.
         *
         * @param coordinatorLayout
         * @param child
         * @param target
         * @param velocityX x 方向的速度
         * @param velocityY y 方向的速度
         * @return
         */
        override fun onNestedPreFling(coordinatorLayout: CoordinatorLayout, child: View, target: View, velocityX: Float, velocityY: Float): Boolean {
            return super.onNestedPreFling(coordinatorLayout, child, target, velocityX, velocityY)
        }

        //可以重写这个方法对子View 进行重新布局
        override fun onLayoutChild(parent: CoordinatorLayout, child: View, layoutDirection: Int): Boolean {
            return super.onLayoutChild(parent, child, layoutDirection)
        }
    }
}